﻿using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.SceneManagement;

public class GameManager : MonoBehaviour
{
    ///甜品相关的成员变量
    #region
    //甜品的种类
    public enum SweetsType 
    { 
        EMPTY,
        NORMAL,
        BARRIER,
        ROW_CLEAR,
        COLUMN_CLEAR,
        RANBOWCANDY,
        COUNT//标记类型
    
    }
    //甜品预制体的字典，我们可以通过字典查看对应甜品的游戏物体
    public Dictionary<SweetsType, GameObject> SweetPrefabDic;
    [System.Serializable]
    public struct SweetPrefab 
    {
        public SweetsType Type;
        public GameObject Prefab;

    
    }
    public SweetPrefab[] SweetPrefabs;

    public GameObject GridPrefab;

    //甜品数组
    private GameSweet[,] sweets;

    //要交换的两个甜品对象
    private GameSweet pressedSweet;
    private GameSweet enteredSweet;
    #endregion
    //单例
    private static GameManager _instance;

    public static GameManager Instance
    {
        get { return GameManager._instance; }
        set { GameManager._instance = value; }
    }
    //大网格的行列数
    public int Xcolumn;//列数
    public int yRow;

    //填充时间
    public float fillTime;

    //有关游戏UI显示的内容
    public Text timeText;

    private float gameTime = 60;

    private bool gameOver;

    public int playScore;

    public Text PlayerScoreText;

    private float addScoreTime;

    private float currentScore ;

    public GameObject gameOverPanel;

    public Text finalScoreText;

    private void Awake()
    {

        _instance = this;
    
    }
	// Use this for initialization
	void Start () {
        //字典的实例化
        SweetPrefabDic = new Dictionary<SweetsType,GameObject>();
        for( int i = 0;i<SweetPrefabs.Length;i++)
        {
            if(!SweetPrefabDic.ContainsKey(SweetPrefabs[i].Type))
            {
                SweetPrefabDic.Add(SweetPrefabs[i].Type, SweetPrefabs[i].Prefab);
                
            }
        }


        for (int x = 0; x < Xcolumn; x++)
        {
            for (int y = 0; y < yRow; y++)
            {
                GameObject chocolate = Instantiate(GridPrefab, CorrectPosition(x,y), Quaternion.identity);
                chocolate.transform.SetParent(transform);
            }
        
        }
        sweets = new GameSweet[Xcolumn, yRow];
        for (int x = 0; x < Xcolumn; x++)
        {
            for (int y = 0; y < yRow; y++)
            {                                                                      // CorrectPosition(x, y)
              
                CreatNewSweet(x, y, SweetsType.EMPTY);
            }

        }
        Destroy(sweets[4, 4].gameObject);
        CreatNewSweet(4, 4, SweetsType.BARRIER);
        StartCoroutine(AllFill());
	}
	
	// Update is called once per frame
	void Update () {

        //if (gameOver)
        //{
        //    return;
        //}
        gameTime -= Time.deltaTime;
        if (gameTime <= 0)
        {
            gameTime = 0;
            //显示失败面板
            //播放失败面板的动画
            gameOverPanel.SetActive(true);
            finalScoreText.text = playScore.ToString();
            gameOver = true;
            //return;
        
        }
        timeText.text = gameTime.ToString("0");

        if (addScoreTime <= 0.05f)
        {
            addScoreTime += Time.deltaTime;
        }
        else
        {
            if (currentScore < playScore)
            {
                currentScore++;
                PlayerScoreText.text = currentScore.ToString();
                addScoreTime = 0;
            }
        
        }
        
	}
    public Vector3 CorrectPosition(int x,int y)
    {   //实例需要实例化巧克力块的x位置 = Gamemanager位置x坐标-大网格长度一半+行列对应x坐标
        //实例需要实例化巧克力块的y位置 = Gamemanager位置y坐标+大网格高度一半-行列对应y坐标
        return new Vector3(transform.position.x - Xcolumn / 2f + x,transform.position.y + yRow / 2f- y);
    
    }
    //产生甜品的方法
    public GameSweet CreatNewSweet(int x, int y, SweetsType type)
    {

        GameObject newSweet = Instantiate(SweetPrefabDic[type], CorrectPosition(x, y), Quaternion.identity);
        newSweet.transform.parent = transform;

        sweets[x, y] = newSweet.GetComponent<GameSweet>();
        sweets[x, y].init(x, y, this, type);
        return sweets[x, y];
    }
    //全部填充的方法
    public IEnumerator AllFill()
    {
        bool needRefill = true;
        while (needRefill)
        {
            yield return new WaitForSeconds(fillTime);
            while (Fill())
            {
                yield return new WaitForSeconds(fillTime);
            }
            //清除所有我们已经匹配好的甜品
            needRefill = ClearAllMatchSweet();
        }
       
    
    }
    //分步填充
    public bool  Fill()
    {
        bool filledNotFinished = false;//判断本次填充是否完成

        for (int y = yRow - 2; y >= 0; y--) 
        {

            for (int x = 0; x < Xcolumn; x++)
            {
                GameSweet sweet = sweets[x, y];//得到当前元素位置的甜品对象

                if (sweet.canMove())//如果无法移动，则无法往下填充
                {
                    GameSweet sweetBelow = sweets[x, y + 1];
                    if (sweetBelow.Type == SweetsType.EMPTY)//垂直填充
                    {
                        Destroy(sweetBelow.gameObject);
                        sweet.MoveCompoment.Move(x, y + 1, fillTime);
                        sweets[x, y + 1] = sweet;
                        CreatNewSweet(x, y, SweetsType.EMPTY);
                        filledNotFinished = true;

                    }
                    else//斜向填充
                    {
                        for (int down = -1; down <= 1; down++)
                        {
                            if (down != 0)
                            {
                                int downX = x + down;
                                if (downX >= 0 && downX < Xcolumn)
                                {
                                    GameSweet downSweet = sweets[downX, y + 1];
                                    if (downSweet.Type == SweetsType.EMPTY)
                                    {
                                        bool canfill = true;//用来判断垂直填充是否可以满足填充要求
                                        for (int aboveY = y; aboveY >= 0; aboveY--)
                                        {
                                            GameSweet sweetAbove = sweets[downX, aboveY];
                                            if (sweetAbove.canMove())
                                            {
                                                break;

                                            }
                                            else if (!sweetAbove.canMove() && sweetAbove.Type != SweetsType.EMPTY)
                                            {
                                                canfill = false;
                                                break;
                                            }
                                        }
                                        if (!canfill)
                                        {
                                            Destroy(downSweet.gameObject);
                                            sweet.MoveCompoment.Move(downX, y + 1, fillTime);
                                            sweets[downX, y + 1] = sweet;
                                            CreatNewSweet(x, y, SweetsType.EMPTY);
                                            filledNotFinished = true;
                                            break;
                                        }
                                    }
                                }
                            }
                        }
                    }

                }
                
            }
        
        }
        //最上排的特殊情况
        for (int x = 0; x < Xcolumn; x++)
        {
           GameSweet sweet = sweets[x, 0];
           if (sweet.Type == SweetsType.EMPTY)
           {
              GameObject newSweet =   Instantiate(SweetPrefabDic[SweetsType.NORMAL], CorrectPosition(x, -1), Quaternion.identity);
              newSweet.transform.parent = transform;

              sweets[x, 0] = newSweet.GetComponent<GameSweet>();
              sweets[x, 0].init(x, -1, this, SweetsType.NORMAL);
              sweets[x, 0].MoveCompoment.Move(x, 0,fillTime);
              sweets[x, 0].ColoredCompoment.SetColor((ColorSweet.ColorType)Random.Range(0, sweets[x, 0].ColoredCompoment.NumColors));
              filledNotFinished = true;
           }
        }
        return filledNotFinished;
    }

    //甜品是否相邻的判断方法
    private bool IsFriend(GameSweet sweet1,GameSweet sweet2)
    {
        return (sweet1.X == sweet2.X && Mathf.Abs(sweet1.Y - sweet2.Y) == 1) || (sweet1.Y == sweet2.Y && Mathf.Abs(sweet1.X - sweet2.X) == 1);
        
    }
    //交换两个甜品的方法
    private void ExchangeSweets(GameSweet sweet1, GameSweet sweet2)
    {
        if (sweet1.canMove() && sweet2.canMove())
        {
            sweets[sweet1.X, sweet1.Y] = sweet2;
            sweets[sweet2.X, sweet2.Y] = sweet1;

            if (MatchSweets(sweet1, sweet2.X, sweet2.Y) != null || MatchSweets(sweet2, sweet1.X, sweet1.Y) != null ||sweet1.Type == SweetsType.RANBOWCANDY || sweet2.Type == SweetsType.RANBOWCANDY)
            {
                int tempX = sweet1.X;
                int tempY = sweet1.Y;

                sweet1.MoveCompoment.Move(sweet2.X, sweet2.Y, fillTime);
                sweet2.MoveCompoment.Move(tempX, tempY, fillTime);

                if (sweet1.Type == SweetsType.RANBOWCANDY && sweet1.CanClear() && sweet2.CanClear())
                {
                    ClearColorSweet clearColor = sweet1.GetComponent<ClearColorSweet>();
                    if (clearColor != null)
                    {
                        clearColor.ClearColor = sweet2.ColoredCompoment.Color;
                    }
                    ClearSweet(sweet1.X, sweet1.Y);

                }
                if (sweet2.Type == SweetsType.RANBOWCANDY && sweet2.CanClear() && sweet1.CanClear())
                {
                    ClearColorSweet clearColor = sweet2.GetComponent<ClearColorSweet>();
                    if (clearColor != null)
                    {
                        clearColor.ClearColor = sweet1.ColoredCompoment.Color;
                    }
                    ClearSweet(sweet2.X, sweet2.Y);

                }
                ClearAllMatchSweet();
                StartCoroutine(AllFill());

                pressedSweet = null;
                enteredSweet = null;

            }
            else
            {
                sweets[sweet1.X, sweet1.Y] = sweet1;
                sweets[sweet2.X, sweet2.Y] = sweet2;
            }
            
        }
        
    }

    /// 玩家对我们甜品方式拖拽处理方法（鼠标）
    #region
    public void PressSweet(GameSweet sweet)
    {
        if (gameOver)
        {
            return;
        }
        pressedSweet = sweet;
    
    }

    public void EnterSweet(GameSweet sweet)
    {
        if (gameOver)
        {
            return;
        }
        enteredSweet = sweet;
    }

    public void ReleaseSweet()
    {
        if (gameOver)
        {
            return;
        }
        if (IsFriend(pressedSweet, enteredSweet))
        {
            ExchangeSweets(pressedSweet, enteredSweet);
        }
        
    }
    #endregion


   
   
    /// 清除匹配的方法
    #region
    //匹配方法
    public List<GameSweet> MatchSweets(GameSweet sweet, int newX, int newY)
    {
        if (sweet.canColor())
        {
            ColorSweet.ColorType color = sweet.ColoredCompoment.Color;
            List<GameSweet> matchRowSweets = new List<GameSweet>();
            List<GameSweet> matchLineSweets = new List<GameSweet>();
            List<GameSweet> finishedMatchingSweets = new List<GameSweet>();

            //行匹配
            matchRowSweets.Add(sweet);
            //i = 0代表往左，i=1代表往右
            for (int i = 0; i <= 1; i++)
            {
                for (int xDistance = 1; xDistance < Xcolumn; xDistance++)
                {
                    int x;
                    if (i == 0)
                    {
                        x = newX - xDistance;
                    }
                    else
                    {
                        x = newX + xDistance;
                    }
                    if (x < 0 || x >= Xcolumn)
                    {
                        break;
                    }
                    if (sweets[x, newY].canColor() && sweets[x, newY].ColoredCompoment.Color == color)
                    {
                        matchRowSweets.Add(sweets[x, newY]);
                    }
                    else
                    {
                        break;
                    }

                }
            }
            if (matchRowSweets.Count >= 3)
            {
                for (int i = 0; i < matchRowSweets.Count; i++)
                {
                    finishedMatchingSweets.Add(matchRowSweets[i]);
                }
            }
            //LT型匹配
            //检查一下当前行遍历列表中数量是否大于三
            if (matchRowSweets.Count >= 3)
            {
                for (int i = 0; i < matchRowSweets.Count; i++)
                {
                    //finishedMatchingSweets.Add(matchRowSweets[i]);
                    //行匹配列表中满足匹配条件的每个元素上下依次进行列遍历
                    //0代表上方，1代表下方
                    for( int j = 0;j <=1;j++)
                    {
                        for (int yDistance = 1; yDistance < yRow; yDistance++)
                        {
                            int y;
                            if (j == 0)
                            {
                                y = newY - yDistance;
                            }
                            else
                            {
                                y = newY + yDistance;
                            }
                            if (y < 0 || y >= yRow)
                            {
                                break;
                            }
                            if (sweets[matchRowSweets[i].X, y].canColor() && sweets[matchRowSweets[i].X, y].ColoredCompoment.Color == color)
                            {
                                matchLineSweets.Add(sweets[matchRowSweets[i].X, y]);
                            }
                            else
                            {
                                break;
                            }
                        }
                    }

                    if (matchLineSweets.Count < 2)
                    {
                        matchLineSweets.Clear();
                    }
                    else
                    {
                        for (int j = 0; j < matchLineSweets.Count; j++)
                        {
                            finishedMatchingSweets.Add(matchLineSweets[j]);
                        }
                        break;
                    
                    }
                }
            
            }
            if (finishedMatchingSweets.Count >= 3)
            {
                return finishedMatchingSweets;
            }
            matchRowSweets.Clear();
            matchLineSweets.Clear();
            //finishedMatchingSweets.Clear();

            matchLineSweets.Add(sweet);


            //列匹配
            
            //i = 0代表往左，i=1代表往右
            for (int i = 0; i <= 1; i++)
            {
                for (int yDistance = 1; yDistance < yRow; yDistance++)
                {
                    int y;
                    if (i == 0)
                    {
                        
                        y = newY - yDistance;
                    }
                    else
                    {
                       
                        y = newY + yDistance;
                    }
                    if (y < 0 || y >= yRow)
                    {
                        break;
                    }
                    if (sweets[newX, y].canColor() && sweets[newX, y].ColoredCompoment.Color == color)
                    {
                        matchLineSweets.Add(sweets[newX, y]);
                    }
                    else
                    {
                        break;
                    }

                }
            }
            //检查一下当前行遍历列表中数量是否大于三
            //if (matchLineSweets.Count >= 3)
            //{
            //    for (int i = 0; i < matchLineSweets.Count; i++)
            //    {
            //        finishedMatchingSweets.Add(matchLineSweets[i]);
            //    }

            //}
            //
            if (matchLineSweets.Count >= 3)
            {
                for (int i = 0; i < matchLineSweets.Count; i++)
                {
                    finishedMatchingSweets.Add(matchLineSweets[i]);
                }
            }
            //LT型匹配
            //检查一下当前行遍历列表中数量是否大于三
            if (matchLineSweets.Count >= 3)
            {
                for (int i = 0; i < matchLineSweets.Count; i++)
                {
                    //finishedMatchingSweets.Add(matchRowSweets[i]);
                    //行匹配列表中满足匹配条件的每个元素上下依次进行列遍历
                    //0代表上方，1代表下方
                    for (int j = 0; j <= 1; j++)
                    {
                        for (int xDistance = 1; xDistance < Xcolumn; xDistance++)
                        {
                            int x;
                            if (j == 0)
                            {
                                x = newY - xDistance;
                            }
                            else
                            {
                                x = newY + xDistance;
                            }
                            if (x < 0 || x >= Xcolumn)
                            {
                                break;
                            }
                            if (sweets[x, matchLineSweets[i].Y].canColor() && sweets[x, matchLineSweets[i].Y].ColoredCompoment.Color == color)
                            {
                                matchRowSweets.Add(sweets[x, matchLineSweets[i].Y]);
                            }
                            else
                            {
                                break;
                            }
                        }
                    }

                    if (matchRowSweets.Count < 2)
                    {
                        matchRowSweets.Clear();
                    }
                    else
                    {
                        for (int j = 0; j < matchRowSweets.Count; j++)
                        {
                            finishedMatchingSweets.Add(matchRowSweets[j]);
                        }
                        break;

                    }
                }

            }
            if (finishedMatchingSweets.Count >= 3)
            {
                return finishedMatchingSweets;
            }
        }
        return null;
    }

    //清除方法
    public bool ClearSweet(int x, int y)
    {
        if (sweets[x, y].CanClear() && !sweets[x, y].ClearedComponent.IsClearing)//?
        {
            sweets[x, y].ClearedComponent.Clear();
            CreatNewSweet(x, y, SweetsType.EMPTY);

            ClearBarrier(x, y);

            return true;
        }
        return false;
    }

    //清除饼干的方法
    public void ClearBarrier(int x,int y)//被消除掉的甜品对象的坐标
    {
        for (int friendX = x - 1; friendX <= x + 1; friendX++)
        {
            if (friendX != x && friendX >= 0 && friendX < Xcolumn)
            {
                if (sweets[friendX, y].Type == SweetsType.BARRIER && sweets[friendX, y].CanClear())
                {
                    sweets[friendX, y].ClearedComponent.Clear();
                    CreatNewSweet(friendX, y, SweetsType.EMPTY);
                }
            }
        }
        for (int friendY = y - 1; friendY <= y + 1; friendY++)
        {
            if (friendY != y && friendY >= 0 && friendY < yRow)
            {
                if (sweets[x, friendY].Type == SweetsType.BARRIER && sweets[x, friendY].CanClear())
                {
                    sweets[x, friendY].ClearedComponent.Clear();
                    CreatNewSweet(x, friendY, SweetsType.EMPTY);
                }
            }
        }
    }

    //清除全部完成匹配的甜品
    private bool ClearAllMatchSweet()
    {
        bool needRefill = false;
        for (int y = 0; y < yRow; y++)
        {
            for (int x = 0; x < Xcolumn; x++)
            {
                if (sweets[x, y].CanClear())
                {
                    List<GameSweet>  matchList =   MatchSweets(sweets[x, y], x, y);
                    if (matchList != null)
                    {
                        SweetsType specialSweetsType = SweetsType.COUNT;//是否产生特殊甜品

                        GameSweet randomSweet = matchList[Random.Range(0, matchList.Count)];
                        int specialSweetx = randomSweet.X;
                        int specialSweety = randomSweet.Y;
                        if (matchList.Count == 4)
                        {
                            specialSweetsType = (SweetsType)Random.Range((int)SweetsType.ROW_CLEAR, (int)SweetsType.COLUMN_CLEAR);
                        }
                        //5个的话我们就产生彩虹糖

                        else if (matchList.Count >= 5)
                        {
                            specialSweetsType = SweetsType.RANBOWCANDY;
                        }
                        for (int i = 0; i < matchList.Count; i++)
                        {
                            if (ClearSweet(matchList[i].X, matchList[i].Y))
                            {
                                needRefill = true;
                            }
                        
                        }
                        if (specialSweetsType != SweetsType.COUNT)
                        {
                            Destroy(sweets[specialSweetx, specialSweety]);
                            GameSweet newSweet = CreatNewSweet(specialSweetx, specialSweety, specialSweetsType);
                            if((specialSweetsType == SweetsType.ROW_CLEAR || specialSweetsType == SweetsType.COLUMN_CLEAR) && newSweet.canColor() && matchList[0].canColor())
                            {
                                newSweet.ColoredCompoment.SetColor(matchList[0].ColoredCompoment.Color);
                            }
                            //加上彩虹糖的特殊类型的产生
                            else if (specialSweetsType == SweetsType.RANBOWCANDY && newSweet.canColor())
                            {
                                newSweet.ColoredCompoment.SetColor(ColorSweet.ColorType.ANY);
                            
                            }
                        }
                    }
                }
            }
        
        }
        return needRefill;
    }
    #endregion

    public void ReturnToMain()
    {
        SceneManager.LoadScene(0);
    
    }
    public void Replay()
    {

        SceneManager.LoadScene(1);
    }
    //清除行的方法
    public void ClearRow(int row)
    {
        for (int x = 0; x < Xcolumn; x++)
        {
            ClearSweet(x, row);
        }
    }
    //清除列的方法
    public void ClearColumn(int column)
    {
        for (int y = 0; y < yRow; y++)
        {
            ClearSweet(column, y);
        }
    }
    //清除颜色的方法
    public void ClearColor(ColorSweet.ColorType color)
    {
        for (int x = 0; x < Xcolumn; x++)
        {
            for (int y = 0; y < yRow; y++)
            {
                if (sweets[x, y].canColor() && (sweets[x, y].ColoredCompoment.Color == color || color == ColorSweet.ColorType.ANY))
                {
                    ClearSweet(x, y);
                }
            }
        }
    }
}
